#define _CRT_SECURE_NO_WARNINGS
#include <stdio.h>
#include <stdlib.h>

#define HASH_SIZE 2000003
#define MAX_OP 1000000

typedef struct HashNode {
    int key;
    int value;
    struct HashNode* next;
} HashNode;

int heap[MAX_OP + 10];
int heap_size = 0;

HashNode* hashTable[HASH_SIZE];

unsigned int hash_function(int key) {
    return (unsigned int)key % HASH_SIZE;
}

void hash_increase(int key) {
    unsigned int idx = hash_function(key);
    HashNode* node = hashTable[idx];
    while (node) {
        if (node->key == key) {
            node->value++;
            return;
        }
        node = node->next;
    }
    HashNode* newNode = (HashNode*)malloc(sizeof(HashNode));
    newNode->key = key;
    newNode->value = 1;
    newNode->next = hashTable[idx];
    hashTable[idx] = newNode;
}

void hash_decrease(int key) {
    unsigned int idx = hash_function(key);
    HashNode* node = hashTable[idx];
    while (node) {
        if (node->key == key) {
            node->value--;
            return;
        }
        node = node->next;
    }
}

int hash_get(int key) {
    unsigned int idx = hash_function(key);
    HashNode* node = hashTable[idx];
    while (node) {
        if (node->key == key) {
            return node->value;
        }
        node = node->next;
    }
    return 0;
}

void swap(int i, int j) {
    int temp = heap[i];
    heap[i] = heap[j];
    heap[j] = temp;
}

void min_heapify(int start) {
    int i = start;
    while (1) {
        int left = 2 * i + 1;
        int right = 2 * i + 2;
        int smallest = i;
        if (left < heap_size && heap[left] < heap[smallest]) {
            smallest = left;
        }
        if (right < heap_size && heap[right] < heap[smallest]) {
            smallest = right;
        }
        if (smallest != i) {
            swap(i, smallest);
            i = smallest;
        }
        else {
            break;
        }
    }
}

void heap_insert(int x) {
    heap[heap_size] = x;
    int i = heap_size;
    heap_size++;
    while (i > 0) {
        int parent = (i - 1) / 2;
        if (heap[parent] > heap[i]) {
            swap(parent, i);
            i = parent;
        }
        else {
            break;
        }
    }
}

void heap_remove_top() {
    swap(0, heap_size - 1);
    heap_size--;
    min_heapify(0);
}

int main() {
    for (int i = 0; i < HASH_SIZE; i++) {
        hashTable[i] = NULL;
    }

    int n;
    scanf("%d", &n);
    int op, x;
    for (int i = 0; i < n; i++) {
        scanf("%d", &op);
        if (op == 1) {
            scanf("%d", &x);
            heap_insert(x);
            hash_increase(x);
        }
        else if (op == 2) {
            while (heap_size > 0) {
                int top = heap[0];
                int freq = hash_get(top);
                if (freq > 0) {
                    printf("%d\n", top);
                    break;
                }
                heap_remove_top();
            }
        }
        else if (op == 3) {
            while (heap_size > 0) {
                int top = heap[0];
                int freq = hash_get(top);
                if (freq > 0) {
                    hash_decrease(top);
                    break;
                }
                heap_remove_top();
            }
        }
    }

    return 0;
}